/*
 * Copyright (C) 2010 The Android Open Source Project
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

package com.smartandroid.sa.sherlock.internal.widget;

import android.app.Activity;
import android.content.Context;
import android.content.pm.ApplicationInfo;
import android.content.pm.PackageManager;
import android.content.pm.PackageManager.NameNotFoundException;
import android.content.res.Configuration;
import android.content.res.TypedArray;
import android.graphics.drawable.Drawable;
import android.os.Build;
import android.os.Parcel;
import android.os.Parcelable;
import android.text.TextUtils;
import android.util.AttributeSet;
import android.util.Log;
import android.view.Gravity;
import android.view.LayoutInflater;
import android.view.MotionEvent;
import android.view.View;
import android.view.ViewGroup;
import android.view.ViewParent;
import android.view.accessibility.AccessibilityEvent;
import android.widget.FrameLayout;
import android.widget.ImageView;
import android.widget.LinearLayout;
import android.widget.SpinnerAdapter;
import android.widget.TextView;

import com.smartandroid.sa.sherlock.app.ActionBar;
import com.smartandroid.sa.sherlock.app.ActionBar.OnNavigationListener;
import com.smartandroid.sa.sherlock.internal.ResourcesCompat;
import com.smartandroid.sa.sherlock.internal.view.menu.ActionMenuItem;
import com.smartandroid.sa.sherlock.internal.view.menu.ActionMenuPresenter;
import com.smartandroid.sa.sherlock.internal.view.menu.ActionMenuView;
import com.smartandroid.sa.sherlock.internal.view.menu.MenuBuilder;
import com.smartandroid.sa.sherlock.internal.view.menu.MenuItemImpl;
import com.smartandroid.sa.sherlock.internal.view.menu.MenuPresenter;
import com.smartandroid.sa.sherlock.internal.view.menu.MenuView;
import com.smartandroid.sa.sherlock.internal.view.menu.SubMenuBuilder;
import com.smartandroid.sa.sherlock.view.CollapsibleActionView;
import com.smartandroid.sa.sherlock.view.Menu;
import com.smartandroid.sa.sherlock.view.MenuItem;
import com.smartandroid.sa.sherlock.view.Window;

import static com.smartandroid.sa.sherlock.internal.ResourcesCompat.getResources_getBoolean;

/**
 * @hide
 */
public class ActionBarView extends AbsActionBarView {
	private static final String TAG = "ActionBarView";

	/**
	 * Display options applied by default
	 */
	public static final int DISPLAY_DEFAULT = 0;
	private Context c;

	/**
	 * Display options that require re-layout as opposed to a simple invalidate
	 */
	private static final int DISPLAY_RELAYOUT_MASK = ActionBar.DISPLAY_SHOW_HOME
			| ActionBar.DISPLAY_USE_LOGO
			| ActionBar.DISPLAY_HOME_AS_UP
			| ActionBar.DISPLAY_SHOW_CUSTOM | ActionBar.DISPLAY_SHOW_TITLE;

	private static final int DEFAULT_CUSTOM_GRAVITY = Gravity.LEFT
			| Gravity.CENTER_VERTICAL;

	private int mNavigationMode;
	private int mDisplayOptions = -1;
	private CharSequence mTitle;
	private CharSequence mSubtitle;
	private Drawable mIcon;
	private Drawable mLogo;

	private HomeView mHomeLayout;
	private HomeView mExpandedHomeLayout;
	private LinearLayout mTitleLayout;
	private TextView mTitleView;
	private TextView mSubtitleView;
	private View mTitleUpView;

	private IcsSpinner mSpinner;
	private IcsLinearLayout mListNavLayout;
	private ScrollingTabContainerView mTabScrollView;
	private View mCustomNavView;
	private IcsProgressBar mProgressView;
	private IcsProgressBar mIndeterminateProgressView;

	private int mProgressBarPadding;
	private int mItemPadding;

	private int mTitleStyleRes;
	private int mSubtitleStyleRes;
	private int mProgressStyle;
	private int mIndeterminateProgressStyle;

	private boolean mUserTitle;
	private boolean mIncludeTabs;
	private boolean mIsCollapsable;
	private boolean mIsCollapsed;

	private MenuBuilder mOptionsMenu;

	private ActionBarContextView mContextView;

	private ActionMenuItem mLogoNavItem;

	private SpinnerAdapter mSpinnerAdapter;
	private OnNavigationListener mCallback;

	// UNUSED private Runnable mTabSelector;

	private ExpandedActionViewMenuPresenter mExpandedMenuPresenter;
	View mExpandedActionView;

	Window.Callback mWindowCallback;

	@SuppressWarnings("rawtypes")
	private final IcsAdapterView.OnItemSelectedListener mNavItemSelectedListener = new IcsAdapterView.OnItemSelectedListener() {
		public void onItemSelected(IcsAdapterView parent, View view,
				int position, long id) {
			if (mCallback != null) {
				mCallback.onNavigationItemSelected(position, id);
			}
		}

		public void onNothingSelected(IcsAdapterView parent) {
			// Do nothing
		}
	};

	private final OnClickListener mExpandedActionViewUpListener = new OnClickListener() {
		@Override
		public void onClick(View v) {
			final MenuItemImpl item = mExpandedMenuPresenter.mCurrentExpandedItem;
			if (item != null) {
				item.collapseActionView();
			}
		}
	};

	private final OnClickListener mUpClickListener = new OnClickListener() {
		public void onClick(View v) {
			mWindowCallback.onMenuItemSelected(Window.FEATURE_OPTIONS_PANEL,
					mLogoNavItem);
		}
	};

	public ActionBarView(Context context, AttributeSet attrs) {
		super(context, attrs);
		this.c = context;

		// Background is always provided by the container.
		setBackgroundResource(0);

		TypedArray a = context.obtainStyledAttributes(
				attrs,
				new int[] { getResources().getIdentifier("SherlockActionBar",
						"styleable", context.getPackageName()) },
				getResources().getIdentifier("actionBarStyle", "attr",
						context.getPackageName()), 0);
		// R.styleable.SherlockActionBar, R.attr.actionBarStyle, 0);

		ApplicationInfo appInfo = context.getApplicationInfo();
		PackageManager pm = context.getPackageManager();
		mNavigationMode = a.getInt(
				getResources().getIdentifier(
						"SherlockActionBar_navigationMode", "styleable",
						context.getPackageName()),
				// R.styleable.SherlockActionBar_navigationMode,
				ActionBar.NAVIGATION_MODE_STANDARD);
		mTitle = a.getText(getResources().getIdentifier(
				"SherlockActionBar_title", "styleable",
				context.getPackageName()));
		// mTitle = a.getText(R.styleable.SherlockActionBar_title);
		mSubtitle = a.getText(getResources().getIdentifier(
				"SherlockActionBar_subtitle", "styleable",
				context.getPackageName()));
		// mSubtitle = a.getText(R.styleable.SherlockActionBar_subtitle);

		mLogo = a.getDrawable(getResources()
				.getIdentifier("SherlockActionBar_logo", "styleable",
						context.getPackageName()));
		// mLogo = a.getDrawable(R.styleable.SherlockActionBar_logo);
		if (mLogo == null) {
			if (Build.VERSION.SDK_INT < Build.VERSION_CODES.HONEYCOMB) {
				if (context instanceof Activity) {
					// Even though native methods existed in API 9 and 10 they
					// don't work
					// so just parse the manifest to look for the logo
					// pre-Honeycomb
					final int resId = ResourcesCompat
							.loadLogoFromManifest((Activity) context);
					if (resId != 0) {
						mLogo = context.getResources().getDrawable(resId);
					}
				}
			} else {
				if (context instanceof Activity) {
					try {
						mLogo = pm.getActivityLogo(((Activity) context)
								.getComponentName());
					} catch (NameNotFoundException e) {
						Log.e(TAG, "Activity component name not found!", e);
					}
				}
				if (mLogo == null) {
					mLogo = appInfo.loadLogo(pm);
				}
			}
		}

		mIcon = a.getDrawable(getResources()
				.getIdentifier("SherlockActionBar_icon", "styleable",
						context.getPackageName()));
		// mIcon = a.getDrawable(R.styleable.SherlockActionBar_icon);
		if (mIcon == null) {
			if (context instanceof Activity) {
				try {
					mIcon = pm.getActivityIcon(((Activity) context)
							.getComponentName());
				} catch (NameNotFoundException e) {
					Log.e(TAG, "Activity component name not found!", e);
				}
			}
			if (mIcon == null) {
				mIcon = appInfo.loadIcon(pm);
			}
		}

		final LayoutInflater inflater = LayoutInflater.from(context);

		final int homeResId = a.getResourceId(
				getResources().getIdentifier("SherlockActionBar_homeLayout",
						"styleable", context.getPackageName()),
				// R.styleable.SherlockActionBar_homeLayout,
				getResources().getIdentifier("abs__action_bar_home",
						"styleable", context.getPackageName()));
		// R.layout.abs__action_bar_home);

		mHomeLayout = (HomeView) inflater.inflate(homeResId, this, false);

		mExpandedHomeLayout = (HomeView) inflater.inflate(homeResId, this,
				false);
		mExpandedHomeLayout.setUp(true);
		mExpandedHomeLayout.setOnClickListener(mExpandedActionViewUpListener);
		mExpandedHomeLayout.setContentDescription(getResources().getText(
				getResources().getIdentifier("abs__action_bar_up_description",
						"string", context.getPackageName())));
		// R.string.abs__action_bar_up_description));

		mTitleStyleRes = a.getResourceId(
				getResources().getIdentifier(
						"SherlockActionBar_titleTextStyle", "styleable",
						context.getPackageName()), 0);
		// R.styleable.SherlockActionBar_titleTextStyle, 0);
		mSubtitleStyleRes = a.getResourceId(
				getResources().getIdentifier(
						"SherlockActionBar_subtitleTextStyle", "styleable",
						context.getPackageName()), 0);
		// R.styleable.SherlockActionBar_subtitleTextStyle, 0);
		mProgressStyle = a.getResourceId(
				getResources().getIdentifier(
						"SherlockActionBar_progressBarStyle", "styleable",
						context.getPackageName()), 0);
		// R.styleable.SherlockActionBar_progressBarStyle, 0);
		mIndeterminateProgressStyle = a.getResourceId(
				getResources().getIdentifier(
						"SherlockActionBar_indeterminateProgressStyle",
						"styleable", context.getPackageName()), 0);
		// R.styleable.SherlockActionBar_indeterminateProgressStyle, 0);

		mProgressBarPadding = a.getDimensionPixelOffset(
				getResources().getIdentifier(
						"SherlockActionBar_progressBarPadding", "styleable",
						context.getPackageName()), 0);
		// R.styleable.SherlockActionBar_progressBarPadding, 0);
		mItemPadding = a.getDimensionPixelOffset(
				getResources().getIdentifier("SherlockActionBar_itemPadding",
						"styleable", context.getPackageName()), 0);
		// R.styleable.SherlockActionBar_itemPadding, 0);

		setDisplayOptions(a.getInt(
				getResources().getIdentifier(
						"SherlockActionBar_displayOptions", "styleable",
						context.getPackageName()), DISPLAY_DEFAULT));
		// R.styleable.SherlockActionBar_displayOptions, DISPLAY_DEFAULT));

		final int customNavId = a.getResourceId(
				getResources().getIdentifier(
						"SherlockActionBar_customNavigationLayout",
						"styleable", context.getPackageName()), 0);
		// R.styleable.SherlockActionBar_customNavigationLayout, 0);
		if (customNavId != 0) {
			mCustomNavView = inflater.inflate(customNavId, this, false);
			mNavigationMode = ActionBar.NAVIGATION_MODE_STANDARD;
			setDisplayOptions(mDisplayOptions | ActionBar.DISPLAY_SHOW_CUSTOM);
		}

		mContentHeight = a.getLayoutDimension(
				getResources().getIdentifier("SherlockActionBar_height",
						"styleable", context.getPackageName()), 0);
		// R.styleable.SherlockActionBar_height, 0);

		a.recycle();

		mLogoNavItem = new ActionMenuItem(context, 0, android.R.id.home, 0, 0,
				mTitle);
		mHomeLayout.setOnClickListener(mUpClickListener);
		mHomeLayout.setClickable(true);
		mHomeLayout.setFocusable(true);
	}

	/*
	 * Must be public so we can dispatch pre-2.2 via ActionBarImpl.
	 */
	@Override
	public void onConfigurationChanged(Configuration newConfig) {
		super.onConfigurationChanged(newConfig);

		mTitleView = null;
		mSubtitleView = null;
		mTitleUpView = null;
		if (mTitleLayout != null && mTitleLayout.getParent() == this) {
			removeView(mTitleLayout);
		}
		mTitleLayout = null;
		if ((mDisplayOptions & ActionBar.DISPLAY_SHOW_TITLE) != 0) {
			initTitle();
		}

		if (mTabScrollView != null && mIncludeTabs) {
			ViewGroup.LayoutParams lp = mTabScrollView.getLayoutParams();
			if (lp != null) {
				lp.width = LayoutParams.WRAP_CONTENT;
				lp.height = LayoutParams.MATCH_PARENT;
			}
			mTabScrollView.setAllowCollapse(true);
		}
	}

	/**
	 * Set the window callback used to invoke menu items; used for dispatching
	 * home button presses.
	 * 
	 * @param cb
	 *            Window callback to dispatch to
	 */
	public void setWindowCallback(Window.Callback cb) {
		mWindowCallback = cb;
	}

	@Override
	public void onDetachedFromWindow() {
		super.onDetachedFromWindow();
		// UNUSED removeCallbacks(mTabSelector);
		if (mActionMenuPresenter != null) {
			mActionMenuPresenter.hideOverflowMenu();
			mActionMenuPresenter.hideSubMenus();
		}
	}

	@Override
	public boolean shouldDelayChildPressedState() {
		return false;
	}

	public void initProgress() {
		mProgressView = new IcsProgressBar(mContext, null, 0, mProgressStyle);
		mProgressView.setId(getResources().getIdentifier(
				"abs__progress_horizontal", "id", c.getPackageName()));
		// mProgressView.setId(R.id.abs__progress_horizontal);
		mProgressView.setMax(10000);
		addView(mProgressView);
	}

	public void initIndeterminateProgress() {
		mIndeterminateProgressView = new IcsProgressBar(mContext, null, 0,
				mIndeterminateProgressStyle);
		mIndeterminateProgressView.setId(getResources().getIdentifier(
				"abs__progress_circular", "id", c.getPackageName()));
		// mIndeterminateProgressView.setId(R.id.abs__progress_circular);
		addView(mIndeterminateProgressView);
	}

	@Override
	public void setSplitActionBar(boolean splitActionBar) {
		if (mSplitActionBar != splitActionBar) {
			if (mMenuView != null) {
				final ViewGroup oldParent = (ViewGroup) mMenuView.getParent();
				if (oldParent != null) {
					oldParent.removeView(mMenuView);
				}
				if (splitActionBar) {
					if (mSplitView != null) {
						mSplitView.addView(mMenuView);
					}
				} else {
					addView(mMenuView);
				}
			}
			if (mSplitView != null) {
				mSplitView.setVisibility(splitActionBar ? VISIBLE : GONE);
			}
			super.setSplitActionBar(splitActionBar);
		}
	}

	public boolean isSplitActionBar() {
		return mSplitActionBar;
	}

	public boolean hasEmbeddedTabs() {
		return mIncludeTabs;
	}

	public void setEmbeddedTabView(ScrollingTabContainerView tabs) {
		if (mTabScrollView != null) {
			removeView(mTabScrollView);
		}
		mTabScrollView = tabs;
		mIncludeTabs = tabs != null;
		if (mIncludeTabs && mNavigationMode == ActionBar.NAVIGATION_MODE_TABS) {
			addView(mTabScrollView);
			ViewGroup.LayoutParams lp = mTabScrollView.getLayoutParams();
			lp.width = LayoutParams.WRAP_CONTENT;
			lp.height = LayoutParams.MATCH_PARENT;
			tabs.setAllowCollapse(true);
		}
	}

	public void setCallback(OnNavigationListener callback) {
		mCallback = callback;
	}

	public void setMenu(Menu menu, MenuPresenter.Callback cb) {
		if (menu == mOptionsMenu)
			return;

		if (mOptionsMenu != null) {
			mOptionsMenu.removeMenuPresenter(mActionMenuPresenter);
			mOptionsMenu.removeMenuPresenter(mExpandedMenuPresenter);
		}

		MenuBuilder builder = (MenuBuilder) menu;
		mOptionsMenu = builder;
		if (mMenuView != null) {
			final ViewGroup oldParent = (ViewGroup) mMenuView.getParent();
			if (oldParent != null) {
				oldParent.removeView(mMenuView);
			}
		}
		if (mActionMenuPresenter == null) {
			mActionMenuPresenter = new ActionMenuPresenter(mContext);
			mActionMenuPresenter.setCallback(cb);
			mActionMenuPresenter.setId(getResources().getIdentifier(
					"abs__action_menu_presenter", "id", c.getPackageName()));
			// mActionMenuPresenter.setId(R.id.abs__action_menu_presenter);
			mExpandedMenuPresenter = new ExpandedActionViewMenuPresenter();
		}

		ActionMenuView menuView;
		final LayoutParams layoutParams = new LayoutParams(
				LayoutParams.WRAP_CONTENT, LayoutParams.MATCH_PARENT);
		if (!mSplitActionBar) {
			mActionMenuPresenter
					.setExpandedActionViewsExclusive(getResources_getBoolean(
							getContext(),
							getResources()
									.getIdentifier(
											"abs__action_bar_expanded_action_views_exclusive",
											"bool", c.getPackageName())));
			// R.bool.abs__action_bar_expanded_action_views_exclusive));
			configPresenters(builder);
			menuView = (ActionMenuView) mActionMenuPresenter.getMenuView(this);
			final ViewGroup oldParent = (ViewGroup) menuView.getParent();
			if (oldParent != null && oldParent != this) {
				oldParent.removeView(menuView);
			}
			addView(menuView, layoutParams);
		} else {
			mActionMenuPresenter.setExpandedActionViewsExclusive(false);
			// Allow full screen width in split mode.
			mActionMenuPresenter.setWidthLimit(getContext().getResources()
					.getDisplayMetrics().widthPixels, true);
			// No limit to the item count; use whatever will fit.
			mActionMenuPresenter.setItemLimit(Integer.MAX_VALUE);
			// Span the whole width
			layoutParams.width = LayoutParams.MATCH_PARENT;
			configPresenters(builder);
			menuView = (ActionMenuView) mActionMenuPresenter.getMenuView(this);
			if (mSplitView != null) {
				final ViewGroup oldParent = (ViewGroup) menuView.getParent();
				if (oldParent != null && oldParent != mSplitView) {
					oldParent.removeView(menuView);
				}
				menuView.setVisibility(getAnimatedVisibility());
				mSplitView.addView(menuView, layoutParams);
			} else {
				// We'll add this later if we missed it this time.
				menuView.setLayoutParams(layoutParams);
			}
		}
		mMenuView = menuView;
	}

	private void configPresenters(MenuBuilder builder) {
		if (builder != null) {
			builder.addMenuPresenter(mActionMenuPresenter);
			builder.addMenuPresenter(mExpandedMenuPresenter);
		} else {
			mActionMenuPresenter.initForMenu(mContext, null);
			mExpandedMenuPresenter.initForMenu(mContext, null);
			mActionMenuPresenter.updateMenuView(true);
			mExpandedMenuPresenter.updateMenuView(true);
		}
	}

	public boolean hasExpandedActionView() {
		return mExpandedMenuPresenter != null
				&& mExpandedMenuPresenter.mCurrentExpandedItem != null;
	}

	public void collapseActionView() {
		final MenuItemImpl item = mExpandedMenuPresenter == null ? null
				: mExpandedMenuPresenter.mCurrentExpandedItem;
		if (item != null) {
			item.collapseActionView();
		}
	}

	public void setCustomNavigationView(View view) {
		final boolean showCustom = (mDisplayOptions & ActionBar.DISPLAY_SHOW_CUSTOM) != 0;
		if (mCustomNavView != null && showCustom) {
			removeView(mCustomNavView);
		}
		mCustomNavView = view;
		if (mCustomNavView != null && showCustom) {
			addView(mCustomNavView);
		}
	}

	public CharSequence getTitle() {
		return mTitle;
	}

	/**
	 * Set the action bar title. This will always replace or override window
	 * titles.
	 * 
	 * @param title
	 *            Title to set
	 * 
	 * @see #setWindowTitle(CharSequence)
	 */
	public void setTitle(CharSequence title) {
		mUserTitle = true;
		setTitleImpl(title);
	}

	/**
	 * Set the window title. A window title will always be replaced or
	 * overridden by a user title.
	 * 
	 * @param title
	 *            Title to set
	 * 
	 * @see #setTitle(CharSequence)
	 */
	public void setWindowTitle(CharSequence title) {
		if (!mUserTitle) {
			setTitleImpl(title);
		}
	}

	private void setTitleImpl(CharSequence title) {
		mTitle = title;
		if (mTitleView != null) {
			mTitleView.setText(title);
			final boolean visible = mExpandedActionView == null
					&& (mDisplayOptions & ActionBar.DISPLAY_SHOW_TITLE) != 0
					&& (!TextUtils.isEmpty(mTitle) || !TextUtils
							.isEmpty(mSubtitle));
			mTitleLayout.setVisibility(visible ? VISIBLE : GONE);
		}
		if (mLogoNavItem != null) {
			mLogoNavItem.setTitle(title);
		}
	}

	public CharSequence getSubtitle() {
		return mSubtitle;
	}

	public void setSubtitle(CharSequence subtitle) {
		mSubtitle = subtitle;
		if (mSubtitleView != null) {
			mSubtitleView.setText(subtitle);
			mSubtitleView.setVisibility(subtitle != null ? VISIBLE : GONE);
			final boolean visible = mExpandedActionView == null
					&& (mDisplayOptions & ActionBar.DISPLAY_SHOW_TITLE) != 0
					&& (!TextUtils.isEmpty(mTitle) || !TextUtils
							.isEmpty(mSubtitle));
			mTitleLayout.setVisibility(visible ? VISIBLE : GONE);
		}
	}

	public void setHomeButtonEnabled(boolean enable) {
		mHomeLayout.setEnabled(enable);
		mHomeLayout.setFocusable(enable);
		// Make sure the home button has an accurate content description for
		// accessibility.
		if (!enable) {
			mHomeLayout.setContentDescription(null);
		} else if ((mDisplayOptions & ActionBar.DISPLAY_HOME_AS_UP) != 0) {
			mHomeLayout.setContentDescription(mContext.getResources().getText(
					getResources().getIdentifier(
							"abs__action_bar_up_description", "string",
							c.getPackageName())));
			// R.string.abs__action_bar_up_description));
		} else {
			mHomeLayout.setContentDescription(mContext.getResources().getText(
					getResources().getIdentifier(
							"abs__action_bar_home_description", "string",
							c.getPackageName())));
			// R.string.abs__action_bar_home_description));
		}
	}

	public void setDisplayOptions(int options) {
		final int flagsChanged = mDisplayOptions == -1 ? -1 : options
				^ mDisplayOptions;
		mDisplayOptions = options;

		if ((flagsChanged & DISPLAY_RELAYOUT_MASK) != 0) {
			final boolean showHome = (options & ActionBar.DISPLAY_SHOW_HOME) != 0;
			final int vis = showHome && mExpandedActionView == null ? VISIBLE
					: GONE;
			mHomeLayout.setVisibility(vis);

			if ((flagsChanged & ActionBar.DISPLAY_HOME_AS_UP) != 0) {
				final boolean setUp = (options & ActionBar.DISPLAY_HOME_AS_UP) != 0;
				mHomeLayout.setUp(setUp);

				// Showing home as up implicitly enables interaction with it.
				// In honeycomb it was always enabled, so make this transition
				// a bit easier for developers in the common case.
				// (It would be silly to show it as up without responding to
				// it.)
				if (setUp) {
					setHomeButtonEnabled(true);
				}
			}

			if ((flagsChanged & ActionBar.DISPLAY_USE_LOGO) != 0) {
				final boolean logoVis = mLogo != null
						&& (options & ActionBar.DISPLAY_USE_LOGO) != 0;
				mHomeLayout.setIcon(logoVis ? mLogo : mIcon);
			}

			if ((flagsChanged & ActionBar.DISPLAY_SHOW_TITLE) != 0) {
				if ((options & ActionBar.DISPLAY_SHOW_TITLE) != 0) {
					initTitle();
				} else {
					removeView(mTitleLayout);
				}
			}

			if (mTitleLayout != null
					&& (flagsChanged & (ActionBar.DISPLAY_HOME_AS_UP | ActionBar.DISPLAY_SHOW_HOME)) != 0) {
				final boolean homeAsUp = (mDisplayOptions & ActionBar.DISPLAY_HOME_AS_UP) != 0;
				mTitleUpView.setVisibility(!showHome ? (homeAsUp ? VISIBLE
						: INVISIBLE) : GONE);
				mTitleLayout.setEnabled(!showHome && homeAsUp);
			}

			if ((flagsChanged & ActionBar.DISPLAY_SHOW_CUSTOM) != 0
					&& mCustomNavView != null) {
				if ((options & ActionBar.DISPLAY_SHOW_CUSTOM) != 0) {
					addView(mCustomNavView);
				} else {
					removeView(mCustomNavView);
				}
			}

			requestLayout();
		} else {
			invalidate();
		}

		// Make sure the home button has an accurate content description for
		// accessibility.
		if (!mHomeLayout.isEnabled()) {
			mHomeLayout.setContentDescription(null);
		} else if ((options & ActionBar.DISPLAY_HOME_AS_UP) != 0) {
			mHomeLayout.setContentDescription(mContext.getResources().getText(
					getResources().getIdentifier(
							"abs__action_bar_up_description", "string",
							c.getPackageName())));
			// R.string.abs__action_bar_up_description));
		} else {
			mHomeLayout.setContentDescription(mContext.getResources().getText(
					getResources().getIdentifier(
							"abs__action_bar_home_description", "string",
							c.getPackageName())));
			// R.string.abs__action_bar_home_description));
		}
	}

	public void setIcon(Drawable icon) {
		mIcon = icon;
		if (icon != null
				&& ((mDisplayOptions & ActionBar.DISPLAY_USE_LOGO) == 0 || mLogo == null)) {
			mHomeLayout.setIcon(icon);
		}
	}

	public void setIcon(int resId) {
		setIcon(mContext.getResources().getDrawable(resId));
	}

	public void setLogo(Drawable logo) {
		mLogo = logo;
		if (logo != null && (mDisplayOptions & ActionBar.DISPLAY_USE_LOGO) != 0) {
			mHomeLayout.setIcon(logo);
		}
	}

	public void setLogo(int resId) {
		setLogo(mContext.getResources().getDrawable(resId));
	}

	public void setNavigationMode(int mode) {
		final int oldMode = mNavigationMode;
		if (mode != oldMode) {
			switch (oldMode) {
			case ActionBar.NAVIGATION_MODE_LIST:
				if (mListNavLayout != null) {
					removeView(mListNavLayout);
				}
				break;
			case ActionBar.NAVIGATION_MODE_TABS:
				if (mTabScrollView != null && mIncludeTabs) {
					removeView(mTabScrollView);
				}
			}

			switch (mode) {
			case ActionBar.NAVIGATION_MODE_LIST:
				if (mSpinner == null) {
					mSpinner = new IcsSpinner(mContext, null, getResources()
							.getIdentifier("actionDropDownStyle", "attr",
									c.getPackageName()));
					// R.attr.actionDropDownStyle);
					mListNavLayout = (IcsLinearLayout) LayoutInflater.from(
							mContext).inflate(
							getResources().getIdentifier(
									"abs__action_bar_tab_bar_view", "layout",
									c.getPackageName()), null);
					// R.layout.abs__action_bar_tab_bar_view, null);
					LinearLayout.LayoutParams params = new LinearLayout.LayoutParams(
							LayoutParams.WRAP_CONTENT,
							LayoutParams.MATCH_PARENT);
					params.gravity = Gravity.CENTER;
					mListNavLayout.addView(mSpinner, params);
				}
				if (mSpinner.getAdapter() != mSpinnerAdapter) {
					mSpinner.setAdapter(mSpinnerAdapter);
				}
				mSpinner.setOnItemSelectedListener(mNavItemSelectedListener);
				addView(mListNavLayout);
				break;
			case ActionBar.NAVIGATION_MODE_TABS:
				if (mTabScrollView != null && mIncludeTabs) {
					addView(mTabScrollView);
				}
				break;
			}
			mNavigationMode = mode;
			requestLayout();
		}
	}

	public void setDropdownAdapter(SpinnerAdapter adapter) {
		mSpinnerAdapter = adapter;
		if (mSpinner != null) {
			mSpinner.setAdapter(adapter);
		}
	}

	public SpinnerAdapter getDropdownAdapter() {
		return mSpinnerAdapter;
	}

	public void setDropdownSelectedPosition(int position) {
		mSpinner.setSelection(position);
	}

	public int getDropdownSelectedPosition() {
		return mSpinner.getSelectedItemPosition();
	}

	public View getCustomNavigationView() {
		return mCustomNavView;
	}

	public int getNavigationMode() {
		return mNavigationMode;
	}

	public int getDisplayOptions() {
		return mDisplayOptions;
	}

	@Override
	protected ViewGroup.LayoutParams generateDefaultLayoutParams() {
		// Used by custom nav views if they don't supply layout params.
		// Everything else
		// added to an ActionBarView should have them already.
		return new ActionBar.LayoutParams(DEFAULT_CUSTOM_GRAVITY);
	}

	@Override
	protected void onFinishInflate() {
		super.onFinishInflate();

		addView(mHomeLayout);

		if (mCustomNavView != null
				&& (mDisplayOptions & ActionBar.DISPLAY_SHOW_CUSTOM) != 0) {
			final ViewParent parent = mCustomNavView.getParent();
			if (parent != this) {
				if (parent instanceof ViewGroup) {
					((ViewGroup) parent).removeView(mCustomNavView);
				}
				addView(mCustomNavView);
			}
		}
	}

	private void initTitle() {
		if (mTitleLayout == null) {
			LayoutInflater inflater = LayoutInflater.from(getContext());
			mTitleLayout = (LinearLayout) inflater.inflate(
					getResources().getIdentifier("abs__action_bar_title_item",
							"layout", c.getPackageName()), this, false);
			// R.layout.abs__action_bar_title_item, this, false);
			mTitleView = (TextView) mTitleLayout.findViewById(getResources()
					.getIdentifier("abs__action_bar_title", "id",
							c.getPackageName()));
			// .findViewById(R.id.abs__action_bar_title);
			mSubtitleView = (TextView) mTitleLayout.findViewById(getResources()
					.getIdentifier("abs__action_bar_subtitle", "id",
							c.getPackageName()));
			// .findViewById(R.id.abs__action_bar_subtitle);
			mTitleUpView = mTitleLayout.findViewById(getResources()
					.getIdentifier("abs__up", "id", c.getPackageName()));
			// mTitleUpView = mTitleLayout.findViewById(R.id.abs__up);

			mTitleLayout.setOnClickListener(mUpClickListener);

			if (mTitleStyleRes != 0) {
				mTitleView.setTextAppearance(mContext, mTitleStyleRes);
			}
			if (mTitle != null) {
				mTitleView.setText(mTitle);
			}

			if (mSubtitleStyleRes != 0) {
				mSubtitleView.setTextAppearance(mContext, mSubtitleStyleRes);
			}
			if (mSubtitle != null) {
				mSubtitleView.setText(mSubtitle);
				mSubtitleView.setVisibility(VISIBLE);
			}

			final boolean homeAsUp = (mDisplayOptions & ActionBar.DISPLAY_HOME_AS_UP) != 0;
			final boolean showHome = (mDisplayOptions & ActionBar.DISPLAY_SHOW_HOME) != 0;
			mTitleUpView.setVisibility(!showHome ? (homeAsUp ? VISIBLE
					: INVISIBLE) : GONE);
			mTitleLayout.setEnabled(homeAsUp && !showHome);
		}

		addView(mTitleLayout);
		if (mExpandedActionView != null
				|| (TextUtils.isEmpty(mTitle) && TextUtils.isEmpty(mSubtitle))) {
			// Don't show while in expanded mode or with empty text
			mTitleLayout.setVisibility(GONE);
		}
	}

	public void setContextView(ActionBarContextView view) {
		mContextView = view;
	}

	public void setCollapsable(boolean collapsable) {
		mIsCollapsable = collapsable;
	}

	public boolean isCollapsed() {
		return mIsCollapsed;
	}

	@Override
	protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
		final int childCount = getChildCount();
		if (mIsCollapsable) {
			int visibleChildren = 0;
			for (int i = 0; i < childCount; i++) {
				final View child = getChildAt(i);
				if (child.getVisibility() != GONE
						&& !(child == mMenuView && mMenuView.getChildCount() == 0)) {
					visibleChildren++;
				}
			}

			if (visibleChildren == 0) {
				// No size for an empty action bar when collapsable.
				setMeasuredDimension(0, 0);
				mIsCollapsed = true;
				return;
			}
		}
		mIsCollapsed = false;

		int widthMode = MeasureSpec.getMode(widthMeasureSpec);
		if (widthMode != MeasureSpec.EXACTLY) {
			throw new IllegalStateException(
					getClass().getSimpleName()
							+ " can only be used "
							+ "with android:layout_width=\"match_parent\" (or fill_parent)");
		}

		int heightMode = MeasureSpec.getMode(heightMeasureSpec);
		if (heightMode != MeasureSpec.AT_MOST) {
			throw new IllegalStateException(getClass().getSimpleName()
					+ " can only be used "
					+ "with android:layout_height=\"wrap_content\"");
		}

		int contentWidth = MeasureSpec.getSize(widthMeasureSpec);

		int maxHeight = mContentHeight > 0 ? mContentHeight : MeasureSpec
				.getSize(heightMeasureSpec);

		final int verticalPadding = getPaddingTop() + getPaddingBottom();
		final int paddingLeft = getPaddingLeft();
		final int paddingRight = getPaddingRight();
		final int height = maxHeight - verticalPadding;
		final int childSpecHeight = MeasureSpec.makeMeasureSpec(height,
				MeasureSpec.AT_MOST);

		int availableWidth = contentWidth - paddingLeft - paddingRight;
		int leftOfCenter = availableWidth / 2;
		int rightOfCenter = leftOfCenter;

		HomeView homeLayout = mExpandedActionView != null ? mExpandedHomeLayout
				: mHomeLayout;

		if (homeLayout.getVisibility() != GONE) {
			final ViewGroup.LayoutParams lp = homeLayout.getLayoutParams();
			int homeWidthSpec;
			if (lp.width < 0) {
				homeWidthSpec = MeasureSpec.makeMeasureSpec(availableWidth,
						MeasureSpec.AT_MOST);
			} else {
				homeWidthSpec = MeasureSpec.makeMeasureSpec(lp.width,
						MeasureSpec.EXACTLY);
			}
			homeLayout.measure(homeWidthSpec,
					MeasureSpec.makeMeasureSpec(height, MeasureSpec.EXACTLY));
			final int homeWidth = homeLayout.getMeasuredWidth()
					+ homeLayout.getLeftOffset();
			availableWidth = Math.max(0, availableWidth - homeWidth);
			leftOfCenter = Math.max(0, availableWidth - homeWidth);
		}

		if (mMenuView != null && mMenuView.getParent() == this) {
			availableWidth = measureChildView(mMenuView, availableWidth,
					childSpecHeight, 0);
			rightOfCenter = Math.max(0,
					rightOfCenter - mMenuView.getMeasuredWidth());
		}

		if (mIndeterminateProgressView != null
				&& mIndeterminateProgressView.getVisibility() != GONE) {
			availableWidth = measureChildView(mIndeterminateProgressView,
					availableWidth, childSpecHeight, 0);
			rightOfCenter = Math.max(0, rightOfCenter
					- mIndeterminateProgressView.getMeasuredWidth());
		}

		final boolean showTitle = mTitleLayout != null
				&& mTitleLayout.getVisibility() != GONE
				&& (mDisplayOptions & ActionBar.DISPLAY_SHOW_TITLE) != 0;

		if (mExpandedActionView == null) {
			switch (mNavigationMode) {
			case ActionBar.NAVIGATION_MODE_LIST:
				if (mListNavLayout != null) {
					final int itemPaddingSize = showTitle ? mItemPadding * 2
							: mItemPadding;
					availableWidth = Math.max(0, availableWidth
							- itemPaddingSize);
					leftOfCenter = Math.max(0, leftOfCenter - itemPaddingSize);
					mListNavLayout.measure(MeasureSpec.makeMeasureSpec(
							availableWidth, MeasureSpec.AT_MOST), MeasureSpec
							.makeMeasureSpec(height, MeasureSpec.EXACTLY));
					final int listNavWidth = mListNavLayout.getMeasuredWidth();
					availableWidth = Math.max(0, availableWidth - listNavWidth);
					leftOfCenter = Math.max(0, leftOfCenter - listNavWidth);
				}
				break;
			case ActionBar.NAVIGATION_MODE_TABS:
				if (mTabScrollView != null) {
					final int itemPaddingSize = showTitle ? mItemPadding * 2
							: mItemPadding;
					availableWidth = Math.max(0, availableWidth
							- itemPaddingSize);
					leftOfCenter = Math.max(0, leftOfCenter - itemPaddingSize);
					mTabScrollView.measure(MeasureSpec.makeMeasureSpec(
							availableWidth, MeasureSpec.AT_MOST), MeasureSpec
							.makeMeasureSpec(height, MeasureSpec.EXACTLY));
					final int tabWidth = mTabScrollView.getMeasuredWidth();
					availableWidth = Math.max(0, availableWidth - tabWidth);
					leftOfCenter = Math.max(0, leftOfCenter - tabWidth);
				}
				break;
			}
		}

		View customView = null;
		if (mExpandedActionView != null) {
			customView = mExpandedActionView;
		} else if ((mDisplayOptions & ActionBar.DISPLAY_SHOW_CUSTOM) != 0
				&& mCustomNavView != null) {
			customView = mCustomNavView;
		}

		if (customView != null) {
			final ViewGroup.LayoutParams lp = generateLayoutParams(customView
					.getLayoutParams());
			final ActionBar.LayoutParams ablp = lp instanceof ActionBar.LayoutParams ? (ActionBar.LayoutParams) lp
					: null;

			int horizontalMargin = 0;
			int verticalMargin = 0;
			if (ablp != null) {
				horizontalMargin = ablp.leftMargin + ablp.rightMargin;
				verticalMargin = ablp.topMargin + ablp.bottomMargin;
			}

			// If the action bar is wrapping to its content height, don't allow
			// a custom
			// view to MATCH_PARENT.
			int customNavHeightMode;
			if (mContentHeight <= 0) {
				customNavHeightMode = MeasureSpec.AT_MOST;
			} else {
				customNavHeightMode = lp.height != LayoutParams.WRAP_CONTENT ? MeasureSpec.EXACTLY
						: MeasureSpec.AT_MOST;
			}
			final int customNavHeight = Math.max(0,
					(lp.height >= 0 ? Math.min(lp.height, height) : height)
							- verticalMargin);

			final int customNavWidthMode = lp.width != LayoutParams.WRAP_CONTENT ? MeasureSpec.EXACTLY
					: MeasureSpec.AT_MOST;
			int customNavWidth = Math.max(0,
					(lp.width >= 0 ? Math.min(lp.width, availableWidth)
							: availableWidth) - horizontalMargin);
			final int hgrav = (ablp != null ? ablp.gravity
					: DEFAULT_CUSTOM_GRAVITY) & Gravity.HORIZONTAL_GRAVITY_MASK;

			// Centering a custom view is treated specially; we try to center
			// within the whole
			// action bar rather than in the available space.
			if (hgrav == Gravity.CENTER_HORIZONTAL
					&& lp.width == LayoutParams.MATCH_PARENT) {
				customNavWidth = Math.min(leftOfCenter, rightOfCenter) * 2;
			}

			customView.measure(MeasureSpec.makeMeasureSpec(customNavWidth,
					customNavWidthMode), MeasureSpec.makeMeasureSpec(
					customNavHeight, customNavHeightMode));
			availableWidth -= horizontalMargin + customView.getMeasuredWidth();
		}

		if (mExpandedActionView == null && showTitle) {
			availableWidth = measureChildView(mTitleLayout, availableWidth,
					MeasureSpec.makeMeasureSpec(mContentHeight,
							MeasureSpec.EXACTLY), 0);
			leftOfCenter = Math.max(0,
					leftOfCenter - mTitleLayout.getMeasuredWidth());
		}

		if (mContentHeight <= 0) {
			int measuredHeight = 0;
			for (int i = 0; i < childCount; i++) {
				View v = getChildAt(i);
				int paddedViewHeight = v.getMeasuredHeight() + verticalPadding;
				if (paddedViewHeight > measuredHeight) {
					measuredHeight = paddedViewHeight;
				}
			}
			setMeasuredDimension(contentWidth, measuredHeight);
		} else {
			setMeasuredDimension(contentWidth, maxHeight);
		}

		if (mContextView != null) {
			mContextView.setContentHeight(getMeasuredHeight());
		}

		if (mProgressView != null && mProgressView.getVisibility() != GONE) {
			mProgressView.measure(MeasureSpec.makeMeasureSpec(contentWidth
					- mProgressBarPadding * 2, MeasureSpec.EXACTLY),
					MeasureSpec.makeMeasureSpec(getMeasuredHeight(),
							MeasureSpec.AT_MOST));
		}
	}

	@Override
	protected void onLayout(boolean changed, int l, int t, int r, int b) {
		int x = getPaddingLeft();
		final int y = getPaddingTop();
		final int contentHeight = b - t - getPaddingTop() - getPaddingBottom();

		if (contentHeight <= 0) {
			// Nothing to do if we can't see anything.
			return;
		}

		HomeView homeLayout = mExpandedActionView != null ? mExpandedHomeLayout
				: mHomeLayout;
		if (homeLayout.getVisibility() != GONE) {
			final int leftOffset = homeLayout.getLeftOffset();
			x += positionChild(homeLayout, x + leftOffset, y, contentHeight)
					+ leftOffset;
		}

		if (mExpandedActionView == null) {
			final boolean showTitle = mTitleLayout != null
					&& mTitleLayout.getVisibility() != GONE
					&& (mDisplayOptions & ActionBar.DISPLAY_SHOW_TITLE) != 0;
			if (showTitle) {
				x += positionChild(mTitleLayout, x, y, contentHeight);
			}

			switch (mNavigationMode) {
			case ActionBar.NAVIGATION_MODE_STANDARD:
				break;
			case ActionBar.NAVIGATION_MODE_LIST:
				if (mListNavLayout != null) {
					if (showTitle)
						x += mItemPadding;
					x += positionChild(mListNavLayout, x, y, contentHeight)
							+ mItemPadding;
				}
				break;
			case ActionBar.NAVIGATION_MODE_TABS:
				if (mTabScrollView != null) {
					if (showTitle)
						x += mItemPadding;
					x += positionChild(mTabScrollView, x, y, contentHeight)
							+ mItemPadding;
				}
				break;
			}
		}

		int menuLeft = r - l - getPaddingRight();
		if (mMenuView != null && mMenuView.getParent() == this) {
			positionChildInverse(mMenuView, menuLeft, y, contentHeight);
			menuLeft -= mMenuView.getMeasuredWidth();
		}

		if (mIndeterminateProgressView != null
				&& mIndeterminateProgressView.getVisibility() != GONE) {
			positionChildInverse(mIndeterminateProgressView, menuLeft, y,
					contentHeight);
			menuLeft -= mIndeterminateProgressView.getMeasuredWidth();
		}

		View customView = null;
		if (mExpandedActionView != null) {
			customView = mExpandedActionView;
		} else if ((mDisplayOptions & ActionBar.DISPLAY_SHOW_CUSTOM) != 0
				&& mCustomNavView != null) {
			customView = mCustomNavView;
		}
		if (customView != null) {
			ViewGroup.LayoutParams lp = customView.getLayoutParams();
			final ActionBar.LayoutParams ablp = lp instanceof ActionBar.LayoutParams ? (ActionBar.LayoutParams) lp
					: null;

			final int gravity = ablp != null ? ablp.gravity
					: DEFAULT_CUSTOM_GRAVITY;
			final int navWidth = customView.getMeasuredWidth();

			int topMargin = 0;
			int bottomMargin = 0;
			if (ablp != null) {
				x += ablp.leftMargin;
				menuLeft -= ablp.rightMargin;
				topMargin = ablp.topMargin;
				bottomMargin = ablp.bottomMargin;
			}

			int hgravity = gravity & Gravity.HORIZONTAL_GRAVITY_MASK;
			// See if we actually have room to truly center; if not push against
			// left or right.
			if (hgravity == Gravity.CENTER_HORIZONTAL) {
				final int centeredLeft = ((getRight() - getLeft()) - navWidth) / 2;
				if (centeredLeft < x) {
					hgravity = Gravity.LEFT;
				} else if (centeredLeft + navWidth > menuLeft) {
					hgravity = Gravity.RIGHT;
				}
			} else if (gravity == -1) {
				hgravity = Gravity.LEFT;
			}

			int xpos = 0;
			switch (hgravity) {
			case Gravity.CENTER_HORIZONTAL:
				xpos = ((getRight() - getLeft()) - navWidth) / 2;
				break;
			case Gravity.LEFT:
				xpos = x;
				break;
			case Gravity.RIGHT:
				xpos = menuLeft - navWidth;
				break;
			}

			int vgravity = gravity & Gravity.VERTICAL_GRAVITY_MASK;

			if (gravity == -1) {
				vgravity = Gravity.CENTER_VERTICAL;
			}

			int ypos = 0;
			switch (vgravity) {
			case Gravity.CENTER_VERTICAL:
				final int paddedTop = getPaddingTop();
				final int paddedBottom = getBottom() - getTop()
						- getPaddingBottom();
				ypos = ((paddedBottom - paddedTop) - customView
						.getMeasuredHeight()) / 2;
				break;
			case Gravity.TOP:
				ypos = getPaddingTop() + topMargin;
				break;
			case Gravity.BOTTOM:
				ypos = getHeight() - getPaddingBottom()
						- customView.getMeasuredHeight() - bottomMargin;
				break;
			}
			final int customWidth = customView.getMeasuredWidth();
			customView.layout(xpos, ypos, xpos + customWidth,
					ypos + customView.getMeasuredHeight());
			x += customWidth;
		}

		if (mProgressView != null) {
			mProgressView.bringToFront();
			final int halfProgressHeight = mProgressView.getMeasuredHeight() / 2;
			mProgressView.layout(mProgressBarPadding, -halfProgressHeight,
					mProgressBarPadding + mProgressView.getMeasuredWidth(),
					halfProgressHeight);
		}
	}

	@Override
	public ViewGroup.LayoutParams generateLayoutParams(AttributeSet attrs) {
		return new ActionBar.LayoutParams(getContext(), attrs);
	}

	@Override
	public ViewGroup.LayoutParams generateLayoutParams(ViewGroup.LayoutParams lp) {
		if (lp == null) {
			lp = generateDefaultLayoutParams();
		}
		return lp;
	}

	@Override
	public Parcelable onSaveInstanceState() {
		Parcelable superState = super.onSaveInstanceState();
		SavedState state = new SavedState(superState);

		if (mExpandedMenuPresenter != null
				&& mExpandedMenuPresenter.mCurrentExpandedItem != null) {
			state.expandedMenuItemId = mExpandedMenuPresenter.mCurrentExpandedItem
					.getItemId();
		}

		state.isOverflowOpen = isOverflowMenuShowing();

		return state;
	}

	@Override
	public void onRestoreInstanceState(Parcelable p) {
		SavedState state = (SavedState) p;

		super.onRestoreInstanceState(state.getSuperState());

		if (state.expandedMenuItemId != 0 && mExpandedMenuPresenter != null
				&& mOptionsMenu != null) {
			final MenuItem item = mOptionsMenu
					.findItem(state.expandedMenuItemId);
			if (item != null) {
				item.expandActionView();
			}
		}

		if (state.isOverflowOpen) {
			postShowOverflowMenu();
		}
	}

	static class SavedState extends BaseSavedState {
		int expandedMenuItemId;
		boolean isOverflowOpen;

		SavedState(Parcelable superState) {
			super(superState);
		}

		private SavedState(Parcel in) {
			super(in);
			expandedMenuItemId = in.readInt();
			isOverflowOpen = in.readInt() != 0;
		}

		@Override
		public void writeToParcel(Parcel out, int flags) {
			super.writeToParcel(out, flags);
			out.writeInt(expandedMenuItemId);
			out.writeInt(isOverflowOpen ? 1 : 0);
		}

		public static final Parcelable.Creator<SavedState> CREATOR = new Parcelable.Creator<SavedState>() {
			public SavedState createFromParcel(Parcel in) {
				return new SavedState(in);
			}

			public SavedState[] newArray(int size) {
				return new SavedState[size];
			}
		};
	}

	public static class HomeView extends FrameLayout {
		private View mUpView;
		private ImageView mIconView;
		private int mUpWidth;
		private Context ct;

		public HomeView(Context context) {
			this(context, null);
			this.ct = context;
		}

		public HomeView(Context context, AttributeSet attrs) {
			super(context, attrs);
			this.ct = context;
		}

		public void setUp(boolean isUp) {
			mUpView.setVisibility(isUp ? VISIBLE : GONE);
		}

		public void setIcon(Drawable icon) {
			mIconView.setImageDrawable(icon);
		}

		@Override
		public boolean dispatchPopulateAccessibilityEvent(
				AccessibilityEvent event) {
			onPopulateAccessibilityEvent(event);
			return true;
		}

		@Override
		public void onPopulateAccessibilityEvent(AccessibilityEvent event) {
			if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.ICE_CREAM_SANDWICH) {
				super.onPopulateAccessibilityEvent(event);
			}
			final CharSequence cdesc = getContentDescription();
			if (!TextUtils.isEmpty(cdesc)) {
				event.getText().add(cdesc);
			}
		}

		@Override
		public boolean dispatchHoverEvent(MotionEvent event) {
			// Don't allow children to hover; we want this to be treated as a
			// single component.
			return onHoverEvent(event);
		}

		@Override
		protected void onFinishInflate() {
			mUpView = findViewById(getResources().getIdentifier("abs__up",
					"id", ct.getPackageName()));
			// mUpView = findViewById(R.id.abs__up);
			mIconView = (ImageView) findViewById(getResources().getIdentifier(
					"abs__home", "id", ct.getPackageName()));
			// mIconView = (ImageView) findViewById(R.id.abs__home);
		}

		public int getLeftOffset() {
			return mUpView.getVisibility() == GONE ? mUpWidth : 0;
		}

		@Override
		protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
			measureChildWithMargins(mUpView, widthMeasureSpec, 0,
					heightMeasureSpec, 0);
			final LayoutParams upLp = (LayoutParams) mUpView.getLayoutParams();
			mUpWidth = upLp.leftMargin + mUpView.getMeasuredWidth()
					+ upLp.rightMargin;
			int width = mUpView.getVisibility() == GONE ? 0 : mUpWidth;
			int height = upLp.topMargin + mUpView.getMeasuredHeight()
					+ upLp.bottomMargin;
			measureChildWithMargins(mIconView, widthMeasureSpec, width,
					heightMeasureSpec, 0);
			final LayoutParams iconLp = (LayoutParams) mIconView
					.getLayoutParams();
			width += iconLp.leftMargin + mIconView.getMeasuredWidth()
					+ iconLp.rightMargin;
			height = Math.max(height,
					iconLp.topMargin + mIconView.getMeasuredHeight()
							+ iconLp.bottomMargin);

			final int widthMode = MeasureSpec.getMode(widthMeasureSpec);
			final int heightMode = MeasureSpec.getMode(heightMeasureSpec);
			final int widthSize = MeasureSpec.getSize(widthMeasureSpec);
			final int heightSize = MeasureSpec.getSize(heightMeasureSpec);

			switch (widthMode) {
			case MeasureSpec.AT_MOST:
				width = Math.min(width, widthSize);
				break;
			case MeasureSpec.EXACTLY:
				width = widthSize;
				break;
			case MeasureSpec.UNSPECIFIED:
			default:
				break;
			}
			switch (heightMode) {
			case MeasureSpec.AT_MOST:
				height = Math.min(height, heightSize);
				break;
			case MeasureSpec.EXACTLY:
				height = heightSize;
				break;
			case MeasureSpec.UNSPECIFIED:
			default:
				break;
			}
			setMeasuredDimension(width, height);
		}

		@Override
		protected void onLayout(boolean changed, int l, int t, int r, int b) {
			final int vCenter = (b - t) / 2;
			// UNUSED int width = r - l;
			int upOffset = 0;
			if (mUpView.getVisibility() != GONE) {
				final LayoutParams upLp = (LayoutParams) mUpView
						.getLayoutParams();
				final int upHeight = mUpView.getMeasuredHeight();
				final int upWidth = mUpView.getMeasuredWidth();
				final int upTop = vCenter - upHeight / 2;
				mUpView.layout(0, upTop, upWidth, upTop + upHeight);
				upOffset = upLp.leftMargin + upWidth + upLp.rightMargin;
				// UNUSED width -= upOffset;
				l += upOffset;
			}
			final LayoutParams iconLp = (LayoutParams) mIconView
					.getLayoutParams();
			final int iconHeight = mIconView.getMeasuredHeight();
			final int iconWidth = mIconView.getMeasuredWidth();
			final int hCenter = (r - l) / 2;
			final int iconLeft = upOffset
					+ Math.max(iconLp.leftMargin, hCenter - iconWidth / 2);
			final int iconTop = Math.max(iconLp.topMargin, vCenter - iconHeight
					/ 2);
			mIconView.layout(iconLeft, iconTop, iconLeft + iconWidth, iconTop
					+ iconHeight);
		}
	}

	private class ExpandedActionViewMenuPresenter implements MenuPresenter {
		MenuBuilder mMenu;
		MenuItemImpl mCurrentExpandedItem;

		@Override
		public void initForMenu(Context context, MenuBuilder menu) {
			// Clear the expanded action view when menus change.
			if (mMenu != null && mCurrentExpandedItem != null) {
				mMenu.collapseItemActionView(mCurrentExpandedItem);
			}
			mMenu = menu;
		}

		@Override
		public MenuView getMenuView(ViewGroup root) {
			return null;
		}

		@Override
		public void updateMenuView(boolean cleared) {
			// Make sure the expanded item we have is still there.
			if (mCurrentExpandedItem != null) {
				boolean found = false;

				if (mMenu != null) {
					final int count = mMenu.size();
					for (int i = 0; i < count; i++) {
						final MenuItem item = mMenu.getItem(i);
						if (item == mCurrentExpandedItem) {
							found = true;
							break;
						}
					}
				}

				if (!found) {
					// The item we had expanded disappeared. Collapse.
					collapseItemActionView(mMenu, mCurrentExpandedItem);
				}
			}
		}

		@Override
		public void setCallback(Callback cb) {
		}

		@Override
		public boolean onSubMenuSelected(SubMenuBuilder subMenu) {
			return false;
		}

		@Override
		public void onCloseMenu(MenuBuilder menu, boolean allMenusAreClosing) {
		}

		@Override
		public boolean flagActionItems() {
			return false;
		}

		@Override
		public boolean expandItemActionView(MenuBuilder menu, MenuItemImpl item) {
			mExpandedActionView = item.getActionView();
			mExpandedHomeLayout.setIcon(mIcon.getConstantState()
					.newDrawable(/* TODO getResources() */));
			mCurrentExpandedItem = item;
			if (mExpandedActionView.getParent() != ActionBarView.this) {
				addView(mExpandedActionView);
			}
			if (mExpandedHomeLayout.getParent() != ActionBarView.this) {
				addView(mExpandedHomeLayout);
			}
			mHomeLayout.setVisibility(GONE);
			if (mTitleLayout != null)
				mTitleLayout.setVisibility(GONE);
			if (mTabScrollView != null)
				mTabScrollView.setVisibility(GONE);
			if (mSpinner != null)
				mSpinner.setVisibility(GONE);
			if (mCustomNavView != null)
				mCustomNavView.setVisibility(GONE);
			requestLayout();
			item.setActionViewExpanded(true);

			if (mExpandedActionView instanceof CollapsibleActionView) {
				((CollapsibleActionView) mExpandedActionView)
						.onActionViewExpanded();
			}

			return true;
		}

		@Override
		public boolean collapseItemActionView(MenuBuilder menu,
				MenuItemImpl item) {
			// Do this before detaching the actionview from the hierarchy, in
			// case
			// it needs to dismiss the soft keyboard, etc.
			if (mExpandedActionView instanceof CollapsibleActionView) {
				((CollapsibleActionView) mExpandedActionView)
						.onActionViewCollapsed();
			}

			removeView(mExpandedActionView);
			removeView(mExpandedHomeLayout);
			mExpandedActionView = null;
			if ((mDisplayOptions & ActionBar.DISPLAY_SHOW_HOME) != 0) {
				mHomeLayout.setVisibility(VISIBLE);
			}
			if ((mDisplayOptions & ActionBar.DISPLAY_SHOW_TITLE) != 0) {
				if (mTitleLayout == null) {
					initTitle();
				} else {
					mTitleLayout.setVisibility(VISIBLE);
				}
			}
			if (mTabScrollView != null
					&& mNavigationMode == ActionBar.NAVIGATION_MODE_TABS) {
				mTabScrollView.setVisibility(VISIBLE);
			}
			if (mSpinner != null
					&& mNavigationMode == ActionBar.NAVIGATION_MODE_LIST) {
				mSpinner.setVisibility(VISIBLE);
			}
			if (mCustomNavView != null
					&& (mDisplayOptions & ActionBar.DISPLAY_SHOW_CUSTOM) != 0) {
				mCustomNavView.setVisibility(VISIBLE);
			}
			mExpandedHomeLayout.setIcon(null);
			mCurrentExpandedItem = null;
			requestLayout();
			item.setActionViewExpanded(false);

			return true;
		}

		@Override
		public int getId() {
			return 0;
		}

		@Override
		public Parcelable onSaveInstanceState() {
			return null;
		}

		@Override
		public void onRestoreInstanceState(Parcelable state) {
		}
	}
}
